package com.taylor.spring5.util;

import com.taylor.spring5.dao.UserDao;
import com.taylor.spring5.dao.UserDaoImpl;

import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;
import java.util.Arrays;

/**
 * @author taylor
 * @Description: jdk代理方式实现方法增强
 * （1）调用 newProxyInstance 方法
 * 方法有三个参数：
 * 第一参数，类加载器
 * 第二参数，增强方法所在的类，这个类实现的接口，支持多个接口
 * 第三参数，实现这个接口 InvocationHandler，创建代理对象，写增强的部分
 *
 * 2 、编写 JDK  动态代理代码
 * （1）创建接口，定义方法
 * （2）创建接口实现类，实现方法
 * （3）使用 Proxy 类创建接口代理对象
 * @date 2021/4/4 22:15
 */
public class JDKProxy {

    public static void main(String[] args) {

        Class[] interfaces = {UserDao.class};

        UserDaoImpl userDao = new UserDaoImpl();
        UserDao proxyInstance = (UserDao)Proxy.newProxyInstance(JDKProxy.class.getClassLoader(), interfaces, new MyProxy(userDao));
        int result = proxyInstance.add(1, 2);
        System.out.println("返回值："+result);
    }


    static class MyProxy implements InvocationHandler{

        Object obj;

        public MyProxy(Object obj) {
            this.obj = obj;
        }

        @Override
        public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {


            String methodName = method.getName();

            //执行方法之前执行
            System.out.println(" before "+ method.getName()+ "参数："+ Arrays.asList(args));

            Object invoke = method.invoke(obj, args);

            System.out.println(" after  "+ obj);
            //执行方法之后执行
            return invoke;
        }
    }
}
